from django.db import models
from django.contrib.auth.models import User
from django.utils import timezone
from typing import TYPE_CHECKING

if TYPE_CHECKING:
    from datetime import datetime, date
    from decimal import Decimal


class QuitSmokingProfile(models.Model):
    """戒烟资料模型"""
    user = models.OneToOneField(User, on_delete=models.CASCADE, verbose_name='用户')
    quit_date = models.DateTimeField(verbose_name='戒烟开始日期')
    cigarettes_per_day = models.IntegerField(verbose_name='每日吸烟数量')
    price_per_pack = models.DecimalField(max_digits=6, decimal_places=2, verbose_name='每包烟价格')
    cigarettes_per_pack = models.IntegerField(default=20, verbose_name='每包烟数量')  # type: ignore[assignment]
    motivation = models.TextField(verbose_name='戒烟动机', blank=True)
    created_at = models.DateTimeField(auto_now_add=True, verbose_name='创建时间')
    updated_at = models.DateTimeField(auto_now=True, verbose_name='更新时间')
    
    class Meta:
        verbose_name = '戒烟资料'
        verbose_name_plural = '戒烟资料'
    
    def __str__(self) -> str:
        if hasattr(self, 'user') and self.user:
            return f'{self.user.username}的戒烟资料'  # type: ignore
        return '戒烟资料'
    
    @property
    def days_quit(self):
        """戒烟天数"""
        if hasattr(self, 'quit_date') and self.quit_date:
            return (timezone.now() - self.quit_date).days  # type: ignore
        return 0
    
    @property
    def money_saved(self):
        """节省金额"""
        try:
            # 确保必要的属性存在且不为None
            if (not hasattr(self, 'cigarettes_per_day') or 
                not hasattr(self, 'cigarettes_per_pack') or 
                not hasattr(self, 'price_per_pack')):
                return 0.0
                
            cigarettes_per_day = getattr(self, 'cigarettes_per_day', 0) or 0
            cigarettes_per_pack = getattr(self, 'cigarettes_per_pack', 20) or 20
            price_per_pack = getattr(self, 'price_per_pack', 0) or 0
            
            # 确保值是数字类型
            cigarettes_per_day = int(cigarettes_per_day) if cigarettes_per_day else 0
            cigarettes_per_pack = int(cigarettes_per_pack) if cigarettes_per_pack else 20
            price_per_pack = float(price_per_pack) if price_per_pack else 0.0
            
            # 确保cigarettes_per_pack不为0，避免除零错误
            if cigarettes_per_pack <= 0:
                return 0.0
                
            daily_cost = (cigarettes_per_day / cigarettes_per_pack) * price_per_pack
            return round(self.days_quit * daily_cost, 2)
        except (TypeError, ValueError, ZeroDivisionError):
            # 捕获任何计算错误并返回默认值
            return 0.0
    
    @property
    def cigarettes_not_smoked(self):
        """未吸烟数量"""
        try:
            if not hasattr(self, 'cigarettes_per_day'):
                return 0
                
            cigarettes_per_day = getattr(self, 'cigarettes_per_day', 0) or 0
            # 确保值是数字类型
            cigarettes_per_day = int(cigarettes_per_day) if cigarettes_per_day else 0
            return self.days_quit * cigarettes_per_day
        except (TypeError, ValueError):
            # 捕获任何计算错误并返回默认值
            return 0


class DailyRecord(models.Model):
    """每日记录模型"""
    MOOD_CHOICES = [
        ('excellent', '非常好'),
        ('good', '好'),
        ('normal', '一般'),
        ('bad', '差'),
        ('terrible', '非常差'),
    ]
    
    user = models.ForeignKey(User, on_delete=models.CASCADE, verbose_name='用户')
    date = models.DateField(verbose_name='日期')
    mood = models.CharField(max_length=20, choices=MOOD_CHOICES, verbose_name='心情')
    cravings_intensity = models.IntegerField(default=0, verbose_name='烟瘾强度(0-10)')  # type: ignore[assignment]
    notes = models.TextField(blank=True, verbose_name='备注')
    relapsed = models.BooleanField(default=False, verbose_name='是否复吸')  # type: ignore[assignment]
    cigarettes_smoked = models.IntegerField(default=0, verbose_name='吸烟数量')  # type: ignore[assignment]
    created_at = models.DateTimeField(auto_now_add=True, verbose_name='创建时间')
    
    class Meta:
        verbose_name = '每日记录'
        verbose_name_plural = '每日记录'
        unique_together = ['user', 'date']
        ordering = ['-date']
    
    def __str__(self) -> str:
        if hasattr(self, 'user') and self.user:
            return f'{self.user.username} - {self.date}'  # type: ignore
        return f'每日记录 - {self.date}'


class Milestone(models.Model):
    """里程碁模型"""
    name = models.CharField(max_length=100, verbose_name='里程碁名称')
    days = models.IntegerField(verbose_name='所需天数')
    description = models.TextField(verbose_name='描述')
    reward_message = models.TextField(verbose_name='奖励信息')
    icon = models.CharField(max_length=50, default='trophy', verbose_name='图标')  # type: ignore[assignment]
    
    class Meta:
        verbose_name = '里程碁'
        verbose_name_plural = '里程碁'
        ordering = ['days']
    
    def __str__(self) -> str:
        return f'{self.name} ({self.days}天)'


class UserMilestone(models.Model):
    """用户里程碁达成记录"""
    user = models.ForeignKey(User, on_delete=models.CASCADE, verbose_name='用户')
    milestone = models.ForeignKey(Milestone, on_delete=models.CASCADE, verbose_name='里程碁')
    achieved_date = models.DateTimeField(verbose_name='达成日期')
    
    class Meta:
        verbose_name = '用户里程碁'
        verbose_name_plural = '用户里程碁'
        unique_together = ['user', 'milestone']
        ordering = ['-achieved_date']
    
    def __str__(self) -> str:
        if hasattr(self, 'user') and self.user and hasattr(self, 'milestone') and self.milestone:
            return f'{self.user.username} - {self.milestone.name}'  # type: ignore
        return '用户里程碑'


class HealthTip(models.Model):
    """健康建议模型"""
    CATEGORY_CHOICES = [
        ('general', '通用建议'),
        ('craving', '应对烟瘾'),
        ('health', '健康知识'),
        ('motivation', '动机激励'),
        ('exercise', '运动建议'),
        ('diet', '饮食建议'),
    ]
    
    title = models.CharField(max_length=200, verbose_name='标题')
    content = models.TextField(verbose_name='内容')
    category = models.CharField(max_length=20, choices=CATEGORY_CHOICES, verbose_name='类别')
    is_active = models.BooleanField(default=True, verbose_name='是否启用')  # type: ignore[assignment]
    created_at = models.DateTimeField(auto_now_add=True, verbose_name='创建时间')
    
    class Meta:
        verbose_name = '健康建议'
        verbose_name_plural = '健康建议'
        ordering = ['-created_at']
    
    def __str__(self) -> str:
        if hasattr(self, 'title') and self.title:
            return str(self.title)
        return '健康建议'


class CravingLog(models.Model):
    """烟瘾记录模型"""
    TRIGGER_CHOICES = [
        ('stress', '压力'),
        ('boredom', '无聊'),
        ('social', '社交场合'),
        ('alcohol', '饮酒'),
        ('coffee', '咖啡'),
        ('meal', '餐后'),
        ('work', '工作'),
        ('other', '其他'),
    ]
    
    user = models.ForeignKey(User, on_delete=models.CASCADE, verbose_name='用户')
    datetime = models.DateTimeField(auto_now_add=True, verbose_name='发生时间')
    intensity = models.IntegerField(verbose_name='强度(1-10)')
    trigger = models.CharField(max_length=20, choices=TRIGGER_CHOICES, verbose_name='触发因素')
    duration_minutes = models.IntegerField(verbose_name='持续时间(分钟)')
    coping_method = models.TextField(verbose_name='应对方法')
    successful = models.BooleanField(verbose_name='是否成功抵御')
    notes = models.TextField(blank=True, verbose_name='备注')
    
    class Meta:
        verbose_name = '烟瘾记录'
        verbose_name_plural = '烟瘾记录'
        ordering = ['-datetime']
    
    def __str__(self) -> str:
        if hasattr(self, 'user') and self.user and hasattr(self, 'datetime') and self.datetime:
            # 获取实际的 datetime 对象
            dt = getattr(self, 'datetime')
            if hasattr(dt, 'strftime'):
                return f'{self.user.username} - {dt.strftime("%Y-%m-%d %H:%M")}'  # type: ignore
        return '烟瘾记录'


class ChatSession(models.Model):
    """AI助手对话会话"""
    user = models.ForeignKey(User, on_delete=models.CASCADE, verbose_name='用户')
    title = models.CharField(max_length=200, verbose_name='会话标题')
    created_at = models.DateTimeField(auto_now_add=True, verbose_name='创建时间')
    updated_at = models.DateTimeField(auto_now=True, verbose_name='更新时间')
    is_active = models.BooleanField(default=True, verbose_name='是否激活')  # type: ignore[assignment]

    class Meta:
        verbose_name = 'AI对话会话'
        verbose_name_plural = 'AI对话会话'
        ordering = ['-updated_at']

    def __str__(self) -> str:
        return f"{self.user.username} - {self.title}"  # type: ignore

    @property
    def preview(self):
        """获取会话预览"""
        last_message = self.messages.filter(message_type='user').first()  # type: ignore
        if last_message:
            return last_message.content[:50] + ('...' if len(last_message.content) > 50 else '')
        return '新会话'


class ChatMessage(models.Model):
    """AI助手对话消息"""
    MESSAGE_TYPES = [
        ('user', '用户消息'),
        ('ai', 'AI回复'),
        ('system', '系统消息')
    ]
    
    FEATURE_TYPES = [
        ('consult', '快速咨询'),
        ('craving', '烟瘾应对'),
        ('mood', '情感支持'),
        ('health', '健康问答'),
        ('general', '通用对话')
    ]

    session = models.ForeignKey(ChatSession, on_delete=models.CASCADE, related_name='messages', verbose_name='会话')
    message_type = models.CharField(max_length=10, choices=MESSAGE_TYPES, verbose_name='消息类型')
    content = models.TextField(verbose_name='消息内容')
    feature = models.CharField(max_length=20, choices=FEATURE_TYPES, default='general', verbose_name='功能类型')  # type: ignore[assignment]
    created_at = models.DateTimeField(auto_now_add=True, verbose_name='创建时间')
    is_helpful = models.BooleanField(null=True, blank=True, verbose_name='是否有用')  # type: ignore
    
    # AI回复相关字段
    response_time = models.FloatField(null=True, blank=True, verbose_name='响应时间(秒)')
    confidence_score = models.FloatField(null=True, blank=True, verbose_name='置信度评分')

    class Meta:
        verbose_name = 'AI对话消息'
        verbose_name_plural = 'AI对话消息'
        ordering = ['-created_at']

    def __str__(self) -> str:
        return f"{self.get_message_type_display()} - {self.content[:30]}"  # type: ignore


class AIKnowledgeBase(models.Model):
    """AI知识库"""
    CATEGORY_CHOICES = [
        ('smoking_cessation', '戒烟指导'),
        ('health_tips', '健康建议'),
        ('psychological_support', '心理支持'),
        ('motivation', '动机激励'),
        ('nutrition', '营养建议'),
        ('exercise', '运动指导'),
        ('relapse_prevention', '复吸预防'),
        ('emergency_help', '紧急求助')
    ]

    title = models.CharField(max_length=200, verbose_name='标题')
    category = models.CharField(max_length=30, choices=CATEGORY_CHOICES, verbose_name='类别')
    content = models.TextField(verbose_name='内容')
    keywords = models.TextField(help_text='用逗号分隔的关键词', verbose_name='关键词')
    priority = models.IntegerField(default=0, verbose_name='优先级')  # type: ignore[assignment]
    is_active = models.BooleanField(default=True, verbose_name='是否启用')  # type: ignore[assignment]
    created_at = models.DateTimeField(auto_now_add=True, verbose_name='创建时间')
    updated_at = models.DateTimeField(auto_now=True, verbose_name='更新时间')

    class Meta:
        verbose_name = 'AI知识库'
        verbose_name_plural = 'AI知识库'
        ordering = ['-priority', '-created_at']

    def __str__(self) -> str:
        return self.title  # type: ignore


class UserFeedback(models.Model):
    """用户反馈"""
    RATING_CHOICES = [
        (1, '很差'),
        (2, '较差'),
        (3, '一般'),
        (4, '较好'),
        (5, '很好')
    ]

    user = models.ForeignKey(User, on_delete=models.CASCADE, verbose_name='用户')
    message = models.ForeignKey(ChatMessage, on_delete=models.CASCADE, verbose_name='相关消息')
    rating = models.IntegerField(choices=RATING_CHOICES, verbose_name='评分')  # type: ignore[assignment]
    comment = models.TextField(blank=True, verbose_name='评论')
    created_at = models.DateTimeField(auto_now_add=True, verbose_name='创建时间')

    class Meta:
        verbose_name = '用户反馈'
        verbose_name_plural = '用户反馈'
        ordering = ['-created_at']

    def __str__(self) -> str:
        return f"{self.user.username} - {self.rating}星"  # type: ignore

